<?php
class JFileGlobals
{
	/**
	 * The raw text of this Globals as it would appear in a JASS File
	 *
	 * @var String
	 */
	private $rawText;
	
	/**
	 * An array repesentation of the global variables, where the key is the variable name, and the value is the variable value.
	 *
	 * @var Array;
	 */
	private $globals = array();
	
	/**
	 * The literal that identifies the start of the globals block
	 *
	 * @var String
	 */
	public static $GLOBALS_START = 'globals';
	
	/**
	 * The literal that identifies the end of the globals block
	 *
	 * @var String
	 */
	public static $GLOBALS_END = 'endglobals';
	
	public function __construct($text)
	{
		$this->rawText = $this->extractGlobalsBlock($text);
		$this->globals = $this->convertRawTextToArray($this->rawText);
	}
	
	/**
	 * Given text, extracts and returns the globals block
	 *
	 * @param String $text
	 * @return String $rawText
	 */
	private function extractGlobalsBlock($text)
	{
		$startPos = strpos($text, JFileGlobals::$GLOBALS_START);
		$stopPos = strpos($text, JFileGlobals::$GLOBALS_END);
		$length = ($stopPos - $startPos + strlen(JFileGlobals::$GLOBALS_END));
		$return = substr($text, $startPos, $length);
		return $return;
	}
	
	/**
	 * Given Globals text, converts into array representation
	 *
	 * @param String $text
	 */
	private function convertRawTextToArray($text)
	{
		//remove start and end identifiers and whitespace
		$trimmedText = trim($this->removeBlockIdentifiers($text));
		$debris = explode("\n", "$trimmedText");
	
		$result = array();
		//go through results and create a new array with key => value 
		foreach($debris as $currentChunk){
			$temp = explode(" ", trim($currentChunk));
			$temp2 = array();
			//clean up the spaces in the array and move to second array
			foreach($temp as $key=>$value){
				if(trim($value)){
					$temp2[] = trim($value);
				}
			}
			
			if(count($temp2) == 2){
				//we have a normal key/value pair
				$result[$temp2[1]] = $temp2[0];
			}else{
				//we have a key array/value pair
				$result[$temp2[2]] = $temp2[0].' '.$temp2[1];
			}
		}

		return $result;
	}
	
	/**
	 * Given a JFileGlobals aray representation, returns the appropriate raw text
	 *
	 * @param Array $globals
	 * @return String
	 */
	private function convertArrayToRawText($globals)
	{
		$result = JFileGlobals::$GLOBALS_START."\n";
		foreach($globals as $value=>$variable){
			$result .= $variable." ".$value."\n";
		}
		$result .= JFileGlobals::$GLOBALS_END."\n";
		
		return $result;
	}
	
	/**
	 * Given a JFileGlobals text, returns the same thing sans the identifiers
	 *
	 * @param String $text
	 * @return String
	 */
	private function removeBlockIdentifiers($text)
	{
		$searchKeys = array(JFileGlobals::$GLOBALS_END, JFileGlobals::$GLOBALS_START);
		$return = str_replace($searchKeys, '', $text);
		return $return;
	}
	
	/**
	 * Returns the array representation of the globals block
	 *
	 * @return Array
	 */
	public function getGlobals()
	{
		return $this->globals;
	}
	
	/**
	 * Gets the raw text.
	 *
	 * @return String
	 */
	public function getRawText()
	{
		return $this->rawText;
	}
	
	/*
	 * Takes a JFileGlobals Object and replaces the calling object's globals array with the combination of both,sorts the result, then updates the resulting raw text.
	 * 
	 * @param JFileGlobals $jFileGlobals
	 */
	public function absorbGlobals(JFileGlobals $jFileGlobals)
	{
		$this->globals = array_merge($this->getGlobals(), $jFileGlobals->getGlobals());
		ksort($this->getGlobals());
		$this->rawText = $this->convertArrayToRawText($this->getGlobals());
	}
}
?>